home *** CD-ROM | disk | FTP | other *** search
/ TOS Silver 2000 / TOS Silver 2000.iso / programm / MM2_DEV / S / MOS / FPUSUPPO.I < prev    next >
Encoding:
Text File  |  1994-02-15  |  9.1 KB  |  3 lines

  1. ⓪ IMPLEMENTATION MODULE FPUSupport;⓪ (*$Y+,X+,F-*)⓪ ⓪ (*⓪!* 27.11.90  Routinen laufen auch, wenn Aufrufer schon im Supervisormode ist.⓪!* 29.07.91  keine Privilegsverletzung mehr, wenn im Usermode (hyperCACHE030);⓪!*           Sprung in Supervisormode nun korrekt (ging bisher gar nicht?!).⓪!*           FSAVE bei externalFPU rettet nun Frame in umgekehrter Reihenfolge,⓪!*           so daß es nun endlich korrekt funktioniert.⓪!* 15.02.94  Keine Low-Byte-Zugriffe mehr auf fpstat wg. Mega STE⓪!*⓪!* >> Konzept noch nicht perfekt: Wenn Coroutinen ggf.automatisch den⓪!*   FPU-Context switchen sollen, würden noch Low-Level-versionen⓪!*   von Save/RestoreContext benötigt. Ggf. "usedFPU", "MaxContextSize"⓪!*   und diese Low-Level Routinen in ein Modul "FPUBase" packen.⓪!*   Die Low-Level-Routinen f. Runtime können hier nicht rein, weil⓪!*   hier Storage importiert wird und das zu zirkul. Importen führt.⓪!*)⓪ ⓪ FROM SYSTEM IMPORT ASSEMBLER, BYTE;⓪ ⓪ FROM Storage IMPORT ALLOCATE, DEALLOCATE;⓪ ⓪ IMPORT MOSGlobals, SFP004;⓪ ⓪ FROM SysInfo IMPORT FPUType, FPU, FPUModel;⓪ ⓪ VAR usedFPU: FPUType;  (* zeigt die verwendete FPU an *)⓪$model: CARDINAL;⓪ ⓪ CONST movemSize = 8*12 + 3*4;⓪&contextSize = movemSize + 2 + 2 + 256 + 4;⓪ ⓪ (* Die Größe errechnet sich aus:⓪!* 8 * FPn (je 12 Byte)⓪!* je 4 für FPCR/SR/IAR⓪!* 2 für evtl. nicht-Null-Flag⓪!* 2 für Frame-Word von FSAVE⓪!* interne Daten bei Busy State Frame (256 max. möglich)⓪!* 4 zur Sicherheit *)⓪ ⓪ TYPE FPUContext = POINTER TO ARRAY [1..contextSize] OF BYTE;⓪ ⓪ ⓪ PROCEDURE NewContext     (VAR context: FPUContext);⓪"BEGIN⓪$NEW (context);⓪$IF context = NIL THEN⓪&ASSEMBLER⓪(TRAP    #6⓪(DC.W    MOSGlobals.OutOfMemory⓪&END;⓪$ELSE⓪&ASSEMBLER⓪(; Illegales State Frame erzeugen⓪(MOVE.L  context(A6),A1⓪(MOVE.L  (A1),A0⓪(MOVE.W  #$FFFF,movemSize(A0)⓪&END;⓪$END;⓪"END NewContext;⓪ ⓪ PROCEDURE DisposeContext (VAR context: FPUContext);⓪"BEGIN⓪$DISPOSE (context)⓪"END DisposeContext;⓪ ⓪ (*$L-*)⓪ ⓪ PROCEDURE FPUInit;⓪"BEGIN⓪$ASSEMBLER⓪(CMPI    #externalFPU,usedFPU⓪(BNE     intern⓪(JMP     SFP004.FPUReset⓪$intern:⓪(CMPI    #internalFPU,usedFPU⓪(BNE     none⓪(FMOVE   #$0000F400,FPCR  ; s. 'Runtime'⓪$none:⓪$END⓪"END FPUInit;⓪ ⓪ (* wird nicht exportiert, da FPUContext eh nur opaque ist und ein manuelles⓪!* allozieren damit gar nicht möglich ist.⓪ PROCEDURE MaxContextSize (): LONGCARD;⓪!(*⓪"* Liefert die maximal nötige Größe des Context-Puffers in Byte.⓪"* Damit kann der Bereich notfalls auf eine andere Weise reserviert⓪"* werden, statt 'NewContext' zu benutzen.⓪"* Dann sollte der für 'FPUContext' angelegte Pu⓪"*)⓪ PROCEDURE MaxContextSize (): LONGCARD;⓪"BEGIN⓪$ASSEMBLER⓪(MOVE.L  #contextSize,(A3)+⓪$END⓪"END MaxContextSize;⓪ *)⓪ ⓪ PROCEDURE AcknowledgeException (context: FPUContext);⓪"BEGIN⓪$ASSEMBLER⓪(; Setze Bit 27 im BIU⓪(MOVE.L  -(A3),A1⓪(CMPI    #internalFPU,usedFPU⓪(BNE     noAckn⓪(LEA     movemSize(A1),A1⓪(TST.B   (A1)⓪(BEQ     noAckn          ; kein Ackn bei Null-State⓪(CLR     D0⓪(MOVE.B  1(A1),D0⓪(BSET    #3,(A1,D0.W)⓪&noAckn⓪$END⓪"END AcknowledgeException;⓪ ⓪ ⓪ CONST   A2stat  =  0;             (* Response word of MC68881 read *)⓪(A2ctrl  =  2;             (* Control  word of MC68881 write *)⓪(A2save  =  4;             (* Save     word of MC68881 read *)⓪(A2restore= 6;             (* Restore  word of MC68881 r/w *)⓪(A2cmd   =  10;            (* Command  word of MC68881 write *)⓪(A2cond  =  14;            (* Condition word of MC68881 write *)⓪(A2op    =  16;            (* Operand  long of MC68881 read/write *)⓪(A2regsel=  $14;           (* register select long read *)⓪ ⓪ PROCEDURE SaveContext    (context: FPUContext);⓪"BEGIN⓪$ASSEMBLER⓪(MOVEQ   #1,D0⓪(MOVE.L  D0,-(A7)⓪(MOVE    #$20,-(A7)⓪(TRAP    #1              ;Super(1)⓪(MOVEQ   #-1,D2⓪(TST     D0              ; sind wir schon im Supervisormode ?⓪(BNE     supv⓪(⓪(MOVE.W  D0,4(A7)⓪(TRAP    #1              ;Super(0)⓪(MOVE.L  D0,A7           ; SSP wiederherstellen⓪(MOVE    #$CFFF,D2⓪&supv⓪(MOVE    SR,D1⓪(AND     D2,D1⓪(MOVE.W  D1,-(A7)⓪(⓪(MOVE.L  -(A3),A1⓪(MOVE.L  A1,A0⓪(ADDA.W  #movemSize,A1⓪(⓪(CMPI    #externalFPU,usedFPU⓪(BNE.W   intern⓪(⓪(MOVE.L  A3,D1⓪(MOVEA.W #$FA40,A2⓪(MOVEA.W #$FA50,A3       ; fpop⓪(⓪ wait    MOVE.W  A2save(A2),D0⓪(CMPI.W  #$300,D0⓪(BCC     start           ; > $300⓪(CMPI.W  #$100,D0⓪(BCS     nullstate       ; < $100⓪(CMPI.W  #$200,D0⓪(BCS     wait⓪(; Format Error⓪(CLR.W   (A1)            ; IDLE-format word sichern⓪(MOVE.L  D1,A3⓪(MOVE.W  (A7)+,SR⓪(ADDQ.L  #6,A7⓪(LINK    A5,#0⓪(JSR     SFP004.FPUError⓪(UNLK    A5⓪(RTS⓪ nullstate:⓪(MOVE.W  D0,(A1)         ; null-format word sichern⓪(BRA.W   endextern⓪ ⓪ start   MOVE.W  D0,(A1)+        ; format word sichern⓪(; Anzahl der Bytes im Lower Byte -> Anz. der Longs berechnen⓪(ANDI    #$FF,D0⓪(ADDA.W  D0,A1⓪(LSR     #2,D0⓪(SUBQ    #1,D0⓪(; während der Datenübertragung des FSAVE keine Interrupts zulassen⓪(MOVE    SR,D2⓪(MOVE    #$2700,SR⓪ loop    MOVE.L  (A3),-(A1)⓪(TST.W   (A2)            ; fpstat wg. Synchr. lesen⓪(DBRA    D0,loop⓪(MOVE    D2,SR⓪(⓪(; FMOVEM FP0-FP7,(A0)+⓪(TST.W   (A2)⓪(MOVE.W  #1111000011111111%,A2cmd(A2)⓪(TST.W   (A2)⓪(TST.W   (A2)⓪(TST.W   A2regsel(A2)⓪(TST.W   (A2)⓪(MOVEQ   #7,D0⓪ again   MOVE.L  (A3),(A0)+⓪(TST.W   (A2)            ; fpstat wg. Synchr. lesen⓪(MOVE.L  (A3),(A0)+⓪(TST.W   (A2)            ; fpstat wg. Synchr. lesen⓪(MOVE.L  (A3),(A0)+⓪(TST.W   (A2)            ; fpstat wg. Synchr. lesen⓪(DBRA    D0,again⓪(⓪(; FMOVEM FPCR/FPSR/FPIAR,(A0)+⓪(MOVE.W  #1011110000000000%,A2cmd(A2)    ;$BC00⓪(TST.W   (A2)⓪(;TST.W   (A2)⓪(;TST.W   A2regsel(A2)⓪(;TST.W   (A2)⓪(MOVE.L  (A3),(A0)+⓪(TST.W   (A2)            ; fpstat wg. Synchr. lesen⓪(MOVE.L  (A3),(A0)+⓪(TST.W   (A2)            ; fpstat wg. Synchr. lesen⓪(MOVE.L  (A3),(A0)+⓪(TST.W   (A2)            ; fpstat wg. Synchr. lesen⓪$endextern:⓪(MOVE.L  D1,A3⓪(BRA     none⓪ ⓪$intern:⓪(CMPI    #internalFPU,usedFPU⓪(BNE     none⓪(FSAVE   (A1)⓪(TST.B   (A1)⓪(BEQ     none⓪(FMOVEM  FP0-FP7,-(A1)⓪(FMOVEM  FPCR/FPSR/FPIAR,-(A1)⓪$none:⓪(MOVE.W  (A7)+,SR⓪(ADDQ.L  #6,A7⓪$END⓪"END SaveContext;⓪ ⓪ PROCEDURE RestoreContext (context: FPUContext);⓪"BEGIN⓪$ASSEMBLER⓪(MOVEQ   #1,D0⓪(MOVE.L  D0,-(A7)⓪(MOVE    #$20,-(A7)⓪(TRAP    #1              ;Super(1)⓪(MOVEQ   #-1,D2⓪(TST     D0              ; sind wir schon im Supervisormode ?⓪(BNE     supv⓪(⓪(MOVE.W  D0,4(A7)⓪(TRAP    #1              ;Super(0)⓪(MOVE.L  D0,A7           ; SSP wiederherstellen⓪(MOVE    #$CFFF,D2⓪&supv⓪(MOVE    SR,D1⓪(AND     D2,D1⓪(MOVE.W  D1,-(A7)⓪(⓪(MOVE.L  -(A3),A1⓪(MOVE.L  A1,A0⓪(ADDA.W  #movemSize,A1⓪(⓪(CMPI    #externalFPU,usedFPU⓪(BNE.W   intern⓪(⓪(TST.B   (A1)⓪(BEQ.W   nullstate⓪(⓪(MOVE.L  A3,D1⓪(MOVEA.W #$FA40,A2⓪(MOVEA.W #$FA50,A3⓪(⓪(; first reset FPU to be able to transfer the regs⓪(MOVE.W  #3,A2ctrl(A2)   ; write abort-cmd⓪(⓪(; FMOVEM (A0)+,FP0-FP7⓪(MOVE.W  #1101000011111111%,A2cmd(A2)⓪(TST.W   (A2)⓪(TST.W   (A2)⓪(TST.W   A2regsel(A2)⓪(TST.W   (A2)⓪(MOVEQ   #7,D0⓪ again   MOVE.L  (A0)+,(A3)⓪(TST.W   (A2)⓪(MOVE.L  (A0)+,(A3)⓪(TST.W   (A2)⓪(MOVE.L  (A0)+,(A3)⓪(TST.W   (A2)⓪(DBRA    D0,again⓪(⓪(; FMOVEM (A0)+,FPCR/FPSR/FPIAR⓪(MOVE.W  #1001110000000000%,A2cmd(A2)⓪(TST.W   (A2)⓪(;TST.W   (A2)⓪(;TST.W   A2regsel(A2)⓪(;TST.W   (A2)⓪(MOVE.L  (A0)+,(A3)⓪(TST.W   (A2)⓪(MOVE.L  (A0)+,(A3)⓪(TST.W   (A2)⓪(MOVE.L  (A0)+,(A3)⓪(TST.W   (A2)⓪ ⓪(; FRESTORE (A1)⓪(MOVE.W  (A1)+,D0⓪(MOVE.W  D0,A2restore(A2)⓪(CMP.W   A2restore(A2),D0⓪(BEQ     start⓪(⓪(MOVE.L  D1,A3⓪(⓪(; Format Error⓪ error   MOVE.W  (A7)+,SR⓪(ADDQ.L  #6,A7⓪(LINK    A5,#0⓪(JSR     SFP004.FPUError⓪(UNLK    A5⓪(RTS⓪ ⓪ nullstate:⓪(MOVEA.W #$FA46,A2       ; fprestore⓪(MOVE.W  (A1),D0⓪(MOVE.W  D0,(A2)         ; FRESTORE⓪(CMP.W   (A2),D0⓪(BEQ     none⓪(BRA     error⓪(⓪ start   ; Anzahl der Bytes im Lower Byte -> Anz. der Longs berechnen⓪(ANDI    #$FF,D0⓪(LSR     #2,D0⓪(SUBQ    #1,D0⓪(; während der Datenübertragung keine Interrupts zulassen⓪(MOVE    SR,D2⓪(MOVE    #$2700,SR⓪ loop    MOVE.L  (A1)+,(A3)⓪(TST.W   (A2)⓪(DBRA    D0,loop⓪(MOVE    D2,SR⓪(MOVE.L  D1,A3⓪(BRA     none⓪(⓪$intern:⓪(CMPI    #internalFPU,usedFPU⓪(BNE     none⓪(TST.B   (A1)⓪(BEQ     null_rst⓪(FMOVEM  (A0)+,FPCR/FPSR/FPIAR⓪(FMOVEM  (A0)+,FP0-FP7⓪$null_rst:⓪(FRESTORE (A1)⓪$none:⓪(MOVE.W  (A7)+,SR⓪(ADDQ.L  #6,A7⓪$END⓪"END RestoreContext;⓪ ⓪ BEGIN⓪"usedFPU:= FPU ();⓪$(* egal, ob die vorhandene FPU auch wirklich benutzt wird: wenn hier⓪%* eine der Funktionen aufgerufen wird, ists auf jeden Fall nicht die⓪%* falsche. *)⓪"model:= FPUModel ();⓪ END FPUSupport.⓪ ə
  2. (* $FFEE3A76$FFEE3A76$FFEE3A76$FFEE3A76$FFEE3A76$FFEE3A76$FFEE3A76$FFEE3A76$FFEE3A76$FFEE3A76$FFEE3A76$000001F9$FFEE3A76$00002226$FFEE3A76$00000893$FFEE3A76$FFEE3A76$FFEE3A76$FFEE3A76$FFEE3A76$FFEE3A76$FFEE3A76$FFEE3A76$FFEE3A76$FFEE3A76$FFEE3A76$FFEE3A76$FFEE3A76$FFEE3A76$FFEE3A76$FFEE3A76$FFEE3A76$FFEE3A76$FFEE3A76$FFEE3A76$FFEE3A76$FFEE3A76$FFEE3A76$FFEE3A76$FFEE3A76$FFEE3A76Ç$000001F3T.......T.......T.......T.......T.......T.......T.......T.......T.......T.......$00001588$00001625$00001715$00001ACA$00001BC4$00001C48$00001CB5$00001D59$00001FFB$0000165D$00001CED$0000003E$000001F9$000001C0$000001F6$000001D4ÇÇé*)
  3.